//
//  CSDNTool.m
//  
//
//  Created by 孟瑞瑞 on 16/5/17.
//  Copyright © 2016年 milan. All rights reserved.
//

#import "CSDNTool.h"
#import "sys/utsname.h"
#include <math.h>
#import <SystemConfiguration/CaptiveNetwork.h>
#import <ifaddrs.h>
#import <arpa/inet.h>
#import <net/if.h>
#import <CoreTelephony/CTCarrier.h>
#import <CoreTelephony/CTTelephonyNetworkInfo.h>



#define IOS_CELLULAR    @"pdp_ip0"
#define IOS_WIFI        @"en0"
#define IOS_VPN         @"utun0"
#define IP_ADDR_IPv4    @"ipv4"
#define IP_ADDR_IPv6    @"ipv6"



//秘钥
static NSString *encryptionKey = @"nha735n197nxn(N′568GGS%d~~9naei';45vhhafdjkv]32rpks;lg,];:vjo(&**&^)";

@implementation CSDNTool

#pragma mark -- 验证码的长度
// 验证验证码的长度
+ (BOOL)isValidCode:(NSString *)code {
    
    return code.length >= 4;
}

#pragma mark -- 验证密码码的长度
// 验证密码的长度
+ (BOOL)isValidPassword:(NSString *)password {
    
    return password.length > 0;
}
#pragma mark -- 验证用户名的长度
// 验证用户名的长度
+ (BOOL)isValidUserName:(NSString *)userName {
    
    return userName.length > 0;
}
+(BOOL)isValidUsernameStr:(NSString *)username{
    NSString *usernameRegx = @"^[a-zA-Z][a-zA-Z0-9_]*$";
       NSPredicate *usernameTest = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", usernameRegx];
       return [usernameTest evaluateWithObject:username];
}

+ (BOOL)isNullToDictionary:(NSDictionary *)dict;
{

    if (dict != nil && ![dict isKindOfClass:[NSNull class]] && dict.count != 0){

        return NO;

    }else{

        return YES;
    }
}
#pragma mark -- 正则判断手机号码格式
//正则判断手机号码格式
+ (BOOL)isValidatePhone:(NSString *)phone
{
    /**
     * 手机号码
     * 移动：134[0-8],135,136,137,138,139,150,151,157,158,159,182,187,188
     * 联通：130,131,132,152,155,156,185,186
     * 电信：133,1349,153,180,189
     */
    NSString * MOBILE = @"^1(3[0-9]|5[0-35-9]|7[068]|8[02345-9])\\d{8}$";
    /**
     10         * 中国移动：China Mobile
     11         * 134[0-8],135,136,137,138,139,150,151,157,158,159,182,187,188
     12         */
    NSString * CM = @"^1(34[0-8]|(3[5-9]|5[017-9]|8[2578])\\d)\\d{7}$";
    /**
     15         * 中国联通：China Unicom
     16         * 130,131,132,152,155,156,185,186
     17         */
    NSString * CU = @"^1(3[0-2]|5[256]|8[56])\\d{8}$";
    /**
     20         * 中国电信：China Telecom
     21         * 133,1349,153,180,189
     22         */
    NSString * CT = @"^1((33|53|8[09])[0-9]|349)\\d{7}$";
    /**
     25         * 大陆地区固话及小灵通
     26         * 区号：010,020,021,022,023,024,025,027,028,029
     27         * 号码：七位或八位
     28         */
    // NSString * PHS = @"^0(10|2[0-5789]|\\d{3})\\d{7,8}$";
    
    NSPredicate *regextestmobile = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", MOBILE];
    NSPredicate *regextestcm = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", CM];
    NSPredicate *regextestcu = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", CU];
    NSPredicate *regextestct = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", CT];
    
    if (([regextestmobile evaluateWithObject:phone] == YES)
        || ([regextestcm evaluateWithObject:phone] == YES)
        || ([regextestct evaluateWithObject:phone] == YES)
        || ([regextestcu evaluateWithObject:phone] == YES))
    {
        if([regextestcm evaluateWithObject:phone] == YES) {
            DDLogDebug(@"China Mobile"); 
        } else if([regextestct evaluateWithObject:phone] == YES) {
            DDLogDebug(@"China Telecom");
        } else if ([regextestcu evaluateWithObject:phone] == YES) {
            DDLogDebug(@"China Unicom");
        } else {
            DDLogDebug(@"Unknow");
        }
        
        return YES;
    }
    else
    {
        return NO;
    }
}

#pragma mark -- 正则判断邮箱格式
//正则判断邮箱格式
+(BOOL)isValidateEmail:(NSString *)email {
    NSString *emailRegex = @"[A-Z0-9a-z._%+-]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,4}";
    NSPredicate *emailTest = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", emailRegex];
    return [emailTest evaluateWithObject:email];
}

#pragma mark --判断手机号合法性

/**
 判断手机号合法性
 
 @param phoneNumber 手机号码
 @param regex 正则
 @return 是否合法
 */
+ (BOOL)checkPhoneNumber:(NSString *)phoneNumber AndRegex:(NSString *)regex

{
    if ([phoneNumber hasPrefix:@"0086"]) {
        phoneNumber = [phoneNumber stringByReplacingCharactersInRange:NSMakeRange(0, 4) withString:@""];
    }
    NSPredicate *pred = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", regex];
    BOOL isMatch = [pred evaluateWithObject:phoneNumber];
    if (!isMatch)
    {
        return NO;
    }
    return YES;
}
 
#pragma mark -- 将颜色转换成图片
//将颜色转换成图片
+ (UIImage *)imageWithColor:(UIColor *)color size:(CGSize)size {
    
    CGRect rect = CGRectMake(0, 0, size.width, size.height);
    
    UIGraphicsBeginImageContext(rect.size);
    
    CGContextRef context = UIGraphicsGetCurrentContext();
    
    CGContextSetFillColorWithColor(context, [color CGColor]);
    
    CGContextFillRect(context, rect);
    
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
    
    UIGraphicsEndImageContext();
    
    
    return image;
    
}



#pragma mark -- 添加提示框
//添加提示框
+ (void)showAlert:(NSString *)alertString inView:(UIView *)view {
    if (view == nil) view = [[UIApplication sharedApplication].windows lastObject];
    
    MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:view animated:YES];
    hud.userInteractionEnabled = NO;
    hud.bezelView.style = MBProgressHUDBackgroundStyleSolidColor;
    hud.bezelView.color = [UIColor colorFromHexCode:@"#1f2124" andAlpha:0.85];
    hud.mode = MBProgressHUDModeCustomView;
    hud.label.text = alertString;
    hud.label.numberOfLines = 0;
    if (DEVICE_IS_IPHONE5||DEVICE_IS_IPHONE4) {
        hud.label.font = [UIFont systemFontOfSize:13];
    }
    else
    {
        hud.label.font = [UIFont systemFontOfSize:14];
    }
    hud.label.textColor = [UIColor colorFromHexCode:@"ffffff"];
    hud.margin = 15.f;
    hud.bezelView.size = CGSizeMake(161, 80);
    hud.minSize = CGSizeMake(127, 80);
    hud.width = 200;
    hud.height = 120;
    hud.center = CGPointMake(view.center.x, view.center.y - 50);
    //    hud.customView = [[UIImageView alloc]initWithImage:[UIImage imageNamed:@"headImage"]];
    //    hud.customView.size = CGSizeMake(22, 22);
    hud.removeFromSuperViewOnHide = YES;
    
    [hud hideAnimated:YES afterDelay:2];
}



#pragma mark -- 添加登录提示框
//添加提示框
+ (void)showLoginAlert:(NSString *)alertString inView:(UIView *)view
{
    if (view == nil) view = [[UIApplication sharedApplication].windows lastObject];
    
    MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:view animated:YES];
    hud.userInteractionEnabled = NO;
    hud.bezelView.style = MBProgressHUDBackgroundStyleSolidColor;
    hud.bezelView.color = [UIColor colorFromHexCode:@"#fff4e0" andAlpha:1.0];
    hud.mode = MBProgressHUDModeCustomView;
    hud.label.text = alertString;
    hud.label.numberOfLines = 0;
    if (DEVICE_IS_IPHONE5||DEVICE_IS_IPHONE4) {
        hud.label.font = [UIFont systemFontOfSize:12];
    }
    else
    {
        hud.label.font = [UIFont systemFontOfSize:12];
    }
    hud.label.textColor = [UIColor colorFromHexCode:@"#FF8800"];
    hud.margin = 15.f;
    hud.bezelView.size = CGSizeMake(161, 32);
    hud.minSize = CGSizeMake(127, 32);
    hud.center = CGPointMake(view.center.x, view.center.y - 50);
    //    hud.customView = [[UIImageView alloc]initWithImage:[UIImage imageNamed:@"headImage"]];
    //    hud.customView.size = CGSizeMake(22, 22);
    hud.removeFromSuperViewOnHide = YES;
    
    [hud hideAnimated:YES afterDelay:3];
}

#pragma mark -- 添加提示框
//添加提示框
+ (void)showImageAlert:(NSString *)alertString inView:(UIView *)view {
    if (view == nil) view = [[UIApplication sharedApplication].windows lastObject];
    
    MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:view animated:YES];
    hud.bezelView.style = MBProgressHUDBackgroundStyleSolidColor;
    hud.bezelView.color = [UIColor colorFromHexCode:@"#1f2124" andAlpha:0.85];
    hud.mode = MBProgressHUDModeCustomView;
    hud.label.text = alertString;
    hud.label.numberOfLines = 0;
    hud.customView = [[UIImageView alloc]initWithImage:[UIImage imageNamed:@"success"]];
    hud.customView.size = CGSizeMake(36, 36);
    if (DEVICE_IS_IPHONE5||DEVICE_IS_IPHONE4) {
        hud.label.font = [UIFont systemFontOfSize:15];
    }
    else
    {
        hud.label.font = [UIFont systemFontOfSize:16];
    }
    hud.label.textColor = [UIColor colorFromHexCode:@"ffffff"];
    hud.margin = 15.f;
    hud.bezelView.size = CGSizeMake(161, 116);
    hud.minSize = CGSizeMake(127, 116);
    hud.center = CGPointMake(view.center.x, view.center.y - 50);
    hud.removeFromSuperViewOnHide = YES;
    
    [hud hideAnimated:YES afterDelay:2];
}

//添加提示框
+ (void)showErrorImageAlert:(NSString *)alertString inView:(UIView *)view {
    if (view == nil) view = [[UIApplication sharedApplication].windows lastObject];
    
    MBProgressHUD *hud = [MBProgressHUD showHUDAddedTo:view animated:YES];
    hud.bezelView.style = MBProgressHUDBackgroundStyleSolidColor;
    hud.bezelView.color = [UIColor colorFromHexCode:@"#1f2124" andAlpha:0.85];
    hud.mode = MBProgressHUDModeCustomView;
    hud.label.text = alertString;
    hud.label.numberOfLines = 0;
    hud.customView = [[UIImageView alloc]initWithImage:[UIImage imageNamed:@"failure"]];
    hud.customView.size = CGSizeMake(36, 36);
    if (DEVICE_IS_IPHONE5||DEVICE_IS_IPHONE4) {
        hud.label.font = [UIFont systemFontOfSize:15];
    }
    else
    {
        hud.label.font = [UIFont systemFontOfSize:16];
    }
    hud.label.textColor = [UIColor colorFromHexCode:@"ffffff"];
    hud.margin = 15.f;
    hud.bezelView.size = CGSizeMake(161, 116);
    hud.minSize = CGSizeMake(127, 116);
    hud.center = CGPointMake(view.center.x, view.center.y - 50);
    
    hud.removeFromSuperViewOnHide = YES;
    
    [hud hideAnimated:YES afterDelay:2];
}

#pragma mark -- md5加密
/**
 *  md5加密
 *
 *  @param str 加密前的字符串
 *
 *  @return 返回加密后的字符串
 */
+(NSString *)md5:(NSString *)str
{
    const char *cStr = [str UTF8String];
    unsigned char result[16];
    CC_MD5(cStr, strlen(cStr), result); // This is the md5 call
    return [NSString stringWithFormat:
            @"%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x",
            result[0], result[1], result[2], result[3],
            result[4], result[5], result[6], result[7],
            result[8], result[9], result[10], result[11],
            result[12], result[13], result[14], result[15]
            ];
}

+(NSString *)md5Encrypt:(NSString *)string{
    const char *cStr = [string UTF8String];
    unsigned char digest[CC_MD5_DIGEST_LENGTH];
    
    CC_MD5(cStr, (CC_LONG)strlen(cStr), digest);
    
    NSMutableString *result = [NSMutableString stringWithCapacity:CC_MD5_DIGEST_LENGTH * 2];
    for (int i = 0; i < CC_MD5_DIGEST_LENGTH; i++) {
        [result appendFormat:@"%02X", digest[i]];
    }
    
    return result;
}

+ (NSString *)md5EncryptWithString:(NSString *)string{
    return [self md5:[NSString stringWithFormat:@"%@%@", encryptionKey, string]];
}

#pragma mark -- base64加密
/**
 *  base64加密
 *
 *  @param str 加密前的字符串
 *
 *  @return 返回加密后的字符串
 */
+ (NSString *)base64Encode:(NSString *)string
{
    //先将string转换成data
    NSData *data = [string dataUsingEncoding:NSUTF8StringEncoding];
    
    NSData *base64Data = [data base64EncodedDataWithOptions:0];
    
    NSString *baseString = [[NSString alloc]initWithData:base64Data encoding:NSUTF8StringEncoding];
    
    return baseString;
}

#pragma mark -- base64解密
/**
 *  base64解密
 *
 *  @param str 加密的字符串
 *
 *  @return 返回加密后的字符串
 */
+ (NSString *)base64Dencode:(NSString *)base64String
{
    NSData *data = [NSData dataWithBase64EncodedString:base64String];
    NSString *string = [[NSString alloc]initWithData:data encoding:NSUTF8StringEncoding];
    
    return string;
}



#pragma mark - 时间转换
/**
 时间转换
 
 @param str 时间
 @return 时间
 */
+ (NSString *)compareCurrentTime:(NSString *)str
{
    
    //把字符串转为NSdate
    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
    NSDate *timeDate = [dateFormatter dateFromString:str];
    
    if (!timeDate) {
        [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm"];
        timeDate = [dateFormatter dateFromString:str];
    }
    
    if (!timeDate) {
        [dateFormatter setDateFormat:@"yyyy-MM-dd"];
        timeDate = [dateFormatter dateFromString:str];
    }
    
    if (!timeDate) {
        return str;
    }
    //得到与当前时间差
    NSTimeInterval timeInterval = [timeDate timeIntervalSinceNow];
    timeInterval = -timeInterval;
    long  temp = 0;
    NSString *result;
    NSCalendar *calendar = [NSCalendar currentCalendar];
    unsigned unitFlag = NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay;
    NSDateComponents *comp1 = [calendar components:unitFlag fromDate:timeDate];
    NSDateComponents *comp2 = [calendar components:unitFlag fromDate:[NSDate dateWithTimeIntervalSinceNow:0]];
    if ([comp1 year] == [comp2 year])//判断是否同一年
    {
        if (timeInterval < 60) {
            result = [NSString stringWithFormat:@"刚刚"];
        }
        else if((temp = timeInterval/60) < 60){
            result = [NSString stringWithFormat:@"%ld分钟前",temp];
        }
        else if((temp = timeInterval/3600) >= 1 && (temp = timeInterval/3600) <24){
            result = [NSString stringWithFormat:@"%ld小时前",temp];
        }
        else if ((temp = timeInterval/3600) >= 24 && (temp = timeInterval/3600) < 48){
            
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"HH:mm"];
            NSString *currentDateString = [dateFormatter stringFromDate:timeDate];
            result = [NSString stringWithFormat:@"昨天 %@",currentDateString];
        }
        //    else if ((temp = timeInterval/3600) > 48 && (temp = timeInterval/3600) < 72){
        //        NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
        //        [dateFormatter setDateFormat:@"HH:mm"];
        //        NSString *currentDateString = [dateFormatter stringFromDate:timeDate];
        //        result = [NSString stringWithFormat:@"前天 %@",currentDateString];
        //    }
        else if((temp = timeInterval/3600/24) <= 9){
            result = [NSString stringWithFormat:@"%ld天前",temp];
        }
        
        else if((temp = timeInterval/3600/24/30) <= 12){
            //result = [NSString stringWithFormat:@"%ld月前",temp];
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"MM月dd日"];
            result = [dateFormatter stringFromDate:timeDate];
        }
        else
        {
            //        temp = timeInterval/3600/24/30/12;
            //        result = [NSString stringWithFormat:@"%ld年前",temp];
            NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
            [dateFormatter setDateFormat:@"yyyy年MM月dd日"];
            result = [dateFormatter stringFromDate:timeDate];
        }
    }
    else
    {
        NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
        [dateFormatter setDateFormat:@"yyyy年MM月dd日"];
        result = [dateFormatter stringFromDate:timeDate];
    }
    
    return  result;
}
+ (NSDate *)getTimeDate:(NSString *)str{
    //把字符串转为NSdate
    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
    NSDate *timeDate = [dateFormatter dateFromString:str];
    
    if (!timeDate) {
        [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm"];
        timeDate = [dateFormatter dateFromString:str];
    }
    
    if (!timeDate) {
        [dateFormatter setDateFormat:@"yyyy-MM-dd"];
        timeDate = [dateFormatter dateFromString:str];
    }
    
    if (timeDate) {
        return timeDate;
    }
    
    return nil;
}
+ (NSString *)getTimeFromTimestamp:(double)time{
    
    //将对象类型的时间转换为NSDate类型
    
    NSDate * myDate=[NSDate dateWithTimeIntervalSince1970:time];
    
    //设置时间格式
    
    NSDateFormatter * formatter=[[NSDateFormatter alloc]init];
    
    [formatter setDateFormat:@"YYYY-MM-dd"];
    
    //将时间转换为字符串
    
    NSString *timeStr=[formatter stringFromDate:myDate];
    
    return timeStr;
    
}

#pragma mark -- 绘制虚线
/**
 ** lineView:	   需要绘制成虚线的view
 ** lineLength:	 虚线的宽度
 ** lineSpacing:	虚线的间距
 ** lineColor:	  虚线的颜色
 **/
+ (void)drawDashLine:(UIView *)lineView lineLength:(int)lineLength lineSpacing:(int)lineSpacing lineColor:(UIColor *)lineColor
{
    CAShapeLayer *shapeLayer = [CAShapeLayer layer];
    [shapeLayer setBounds:lineView.bounds];
    [shapeLayer setPosition:CGPointMake(CGRectGetWidth(lineView.frame) / 2, CGRectGetHeight(lineView.frame))];
    [shapeLayer setFillColor:[UIColor clearColor].CGColor];
    //  设置虚线颜色为blackColor
    [shapeLayer setStrokeColor:lineColor.CGColor];
    //  设置虚线宽度
    [shapeLayer setLineWidth:CGRectGetHeight(lineView.frame)];
    [shapeLayer setLineJoin:kCALineJoinRound];
    //  设置线宽，线间距
    [shapeLayer setLineDashPattern:[NSArray arrayWithObjects:[NSNumber numberWithInt:lineLength], [NSNumber numberWithInt:lineSpacing], nil]];
    //  设置路径
    CGMutablePathRef path = CGPathCreateMutable();
    CGPathMoveToPoint(path, NULL, 0, 0);
    CGPathAddLineToPoint(path, NULL, CGRectGetWidth(lineView.frame), 0);
    [shapeLayer setPath:path];
    CGPathRelease(path);
    //  把绘制好的虚线添加上来
    [lineView.layer addSublayer:shapeLayer];
}

#pragma mark -- 获取当前时间
//获取当前时间
+ (NSString *)nowTime{
    NSDate *  senddate = [NSDate date];
    NSDateFormatter  *dateformatter=[[NSDateFormatter alloc] init];
    [dateformatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
    NSString *  nowTimeString=[dateformatter stringFromDate:senddate];
    return nowTimeString;
}

#pragma mark -- 获取NetWork当前时间
+ (NSString *)netWorkNowTime{
    NSDate *  senddate = [NSDate date];
    NSDateFormatter  *dateformatter=[[NSDateFormatter alloc] init];
    [dateformatter setDateFormat:@"yyyy-MM-dd HH:mm"];
    NSString *  nowTimeString=[dateformatter stringFromDate:senddate];
    return nowTimeString;
}


#pragma mark --超过count时，截取字符
//超过count时，截取字符
+(NSInteger)charAtIndexByCount:(NSString *)string withCount:(NSInteger)count
{
    int i;
    int sum=0;
    int count2=0;
    for(i=0;i<[string length];i++)
    {
        unichar str = [string characterAtIndex:i];
        if(str < 256){
            sum+=1;
        }
        else {
            sum+=2;
        }
        count2++;
        if (sum>=count){
            break;
        }
    }
    if(sum>count){
        return count2-1;
    }
    else
        return count2;
}

#pragma mark --按要求截取字符串
//按要求截取字符串
+(NSString *)stringAtIndexByCount:(NSString *)string withCount:(NSInteger)count
{
    int i;
    int sum=0;
    for(i=0;i<[string length];i++)
    {
        unichar str = [string characterAtIndex:i];
        if(str < 256){
            sum+=1;
        }
        else {
            sum+=2;
        }
        if(sum>count){
            //当字符大于count时，剪取三个位置，显示省略号。否则正常显示
            NSString * str=[string substringWithRange:NSMakeRange(0,[self charAtIndexByCount:string withCount:count-3])];
            
            return [NSString stringWithFormat:@"%@...",str];
        }
    }
    return string;
}

#pragma mark -- Encoded 转码
//编码
+(NSString *)URLEncodedString:(NSString *)str
{
    NSString *encodedString = (NSString *)
    CFBridgingRelease(CFURLCreateStringByAddingPercentEscapes(kCFAllocatorDefault,
                                                              (CFStringRef)str,
                                                              NULL,
                                                              (CFStringRef)@"!*'();:@&=+$,/?%#[]",
                                                              kCFStringEncodingUTF8));
    
    return encodedString;
}
//解码
+(NSString *)URLDecodedString:(NSString *)str
{
    NSString *decodedString=(__bridge_transfer NSString *)CFURLCreateStringByReplacingPercentEscapesUsingEncoding(NULL, (__bridge CFStringRef)str, CFSTR(""), CFStringConvertNSStringEncodingToEncoding(NSUTF8StringEncoding));
    
    return decodedString;
}

#pragma mark//Unicode转汉字   \u5f20\u4e09 → 张三
+(NSString *)replaceUnicode:(NSString *)unicodeStr {
    //张三  \u5f20\u4e09
    
    NSString *tempStr1 = [unicodeStr stringByReplacingOccurrencesOfString:@"\\u" withString:@"\\U"];
    NSString *tempStr2 = [tempStr1 stringByReplacingOccurrencesOfString:@"\"" withString:@"\\\""];
    NSString *tempStr3 = [[@"\"" stringByAppendingString:tempStr2] stringByAppendingString:@"\""];
    NSData *tempData = [tempStr3 dataUsingEncoding:NSUTF8StringEncoding];
    NSString* returnStr = [NSPropertyListSerialization propertyListWithData:tempData options:NSPropertyListImmutable format:NULL error:NULL];
    
    
    //  NSLog(@"Output = %@", returnStr);
    return [returnStr stringByReplacingOccurrencesOfString:@"\\r\\n" withString:@"\n"];
}
#pragma mark//汉字转 Unicode   张三 →  \u5f20\u4e09
+(NSString *)utf8ToUnicode:(NSString *)string{
    
    NSUInteger length = [string length];
    NSMutableString *s = [NSMutableString stringWithCapacity:0];
    for (int i = 0;i < length; i++){
        unichar _char = [string characterAtIndex:i];
        //判断是否为英文和数字
        if (_char <= '9' && _char >='0'){
            [s appendFormat:@"%@",[string substringWithRange:NSMakeRange(i,1)]];
        }else if(_char >='a' && _char <= 'z'){
            [s appendFormat:@"%@",[string substringWithRange:NSMakeRange(i,1)]];
        }else if(_char >='A' && _char <= 'Z')
        {
            [s appendFormat:@"%@",[string substringWithRange:NSMakeRange(i,1)]];
        }else{
            [s appendFormat:@"\\u%x",[string characterAtIndex:i]];
        }
    }
    return s;
}


+ (BOOL)is32bit

{
    
#if defined(__LP64__) && __LP64__
    
    return NO;
    
#else
    
    return YES;
    
#endif
    
}

#pragma mark -- 清除路径下文件:
+(void)clearCache:(NSString *)path{
    NSFileManager *fileManager=[NSFileManager defaultManager];
    if ([fileManager fileExistsAtPath:path]) {
        NSArray *childerFiles=[fileManager subpathsAtPath:path];
        for (NSString *fileName in childerFiles) {
            //如有需要，加入条件，过滤掉不想删除的文件
            NSString *absolutePath=[path stringByAppendingPathComponent:fileName];
            [fileManager removeItemAtPath:absolutePath error:nil];
        }
    }
    
    
}

#pragma mark -- 计算路径下文件大小:
+(float)fileSizeAtPath:(NSString *)path{
    NSFileManager *fileManager=[NSFileManager defaultManager];
    if([fileManager fileExistsAtPath:path]){
        long long size=[fileManager attributesOfItemAtPath:path error:nil].fileSize;
        return size/1024.0/1024.0;
    }
    return 0;
}

#pragma mark -- 计算整个路径下及其子文件夹下文件大小:
+(float)fileSizeAtPathInFilePath:(NSString *)path
{
    NSFileManager *fileManager=[NSFileManager defaultManager];
    float folderSize = 0.0;
    if ([fileManager fileExistsAtPath:path])
    {
        NSArray *childerFiles=[fileManager subpathsAtPath:path];
        for (NSString *fileName in childerFiles) {
            NSString *absolutePath=[path stringByAppendingPathComponent:fileName];
            folderSize = folderSize + [CSDNTool fileSizeAtPath:absolutePath];
        }
        return folderSize;
    }
    return 0;
}

#pragma mark -- 排序
//排序
NSInteger customSortTool(id obj1, id obj2,void* context){
    if ([obj1 doubleValue] > [obj2 doubleValue]) {
        return (NSComparisonResult)NSOrderedDescending;
    }
    
    if ([obj1 doubleValue] < [obj2 doubleValue]) {
        return (NSComparisonResult)NSOrderedAscending;
    }
    return (NSComparisonResult)NSOrderedSame;
}

#pragma mark -- 计算最大值
/**
 修改最大值
 
 @param chartValueMax 图表轴的最大值
 @return 最大值
 */
+ (double)getChartValueMax:(double)chartValueMax
{
    double max = 0;
    if (chartValueMax == 0)
    {
        max = 1;
    }
    else if (chartValueMax >= 30)
    {
        
        max = (floor(chartValueMax/10) + 1)*10;
        DDLogDebug(@"%lf",floor(chartValueMax/11));
        if (chartValueMax/10 >= 0.8) {
            max = max + ceil((floor(chartValueMax/10)+1)/4)*10;
        }
        
    }
    else if (chartValueMax <= 0.1)
    {
        max = ceil(chartValueMax/0.005)* 0.005;
        if (ceil(chartValueMax/0.005) >= 2 || chartValueMax/0.005 >= 0.8) {
            max = max + ceil(ceil(chartValueMax/0.005)/4)*0.005;
        }
    }
    else if (chartValueMax <= 1)
    {
        max = ceil(chartValueMax/0.1)* 0.1;
        if (ceil(chartValueMax/0.1) >= 2 || chartValueMax/0.10 >= 0.8) {
            max = max + ceil(ceil(chartValueMax/0.1)/4)*0.1;
        }
    }
    else
    {
        max = ceil(chartValueMax/1)* 1;
        if (ceil(chartValueMax/1) >= 2 || chartValueMax/1.0 >= 0.8) {
            max = max + ceil(ceil(chartValueMax/1)/4)*1;
        }
    }
    return max;
}

#pragma mark -- 根据字符串的的长度来计算UITextView的高度
/**
 
 @return 根据字符串的的长度来计算UITextView的高度
 */
+(float)heightForString:(NSString *)value fontSize:(float)fontSize andWidth:(float)width
{
    float height = [[NSString stringWithFormat:@"%@\n",value] boundingRectWithSize:CGSizeMake(width, CGFLOAT_MAX) options:NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingUsesFontLeading attributes:[NSDictionary dictionaryWithObjectsAndKeys:[UIFont systemFontOfSize:fontSize],NSFontAttributeName, nil] context:nil].size.height;
    
    return height;
}

#pragma mark -- 字典转json格式字符串
//字典转json格式字符串：
+ (NSString*)dictionaryToJson:(NSDictionary *)dic
{
    NSError *parseError = nil;
    NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dic options:NSJSONWritingPrettyPrinted error:&parseError];
    
    return [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
}

#pragma mark -- json格式字符串转字典
//json格式字符串转字典：
+ (NSDictionary *)dictionaryWithJsonString:(NSString *)jsonString {
    
    if (jsonString == nil) {
        
        return nil;
        
    }
    
    NSData *jsonData = [jsonString dataUsingEncoding:NSUTF8StringEncoding];
    
    NSError *err;
    
    NSDictionary *dic = [NSJSONSerialization JSONObjectWithData:jsonData
                         
                                                        options:NSJSONReadingMutableContainers
                         
                                                          error:&err];
    
    if(err) {
        
        DDLogDebug(@"json解析失败：%@",err);
        
        return nil;
        
    }
    
    return dic;
}

#pragma mark 字典转json字符串，并直接过滤掉里面的非法字符
+ (NSString*)dictionaryToUnescapedCharacterJson:(NSDictionary *)dic
{
    NSError *error;
    
    NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dic options:NSJSONWritingPrettyPrinted error:&error];
    
    NSString *jsonString;
    
    if (!jsonData) {
        
        DDLogDebug(@"%@",error);
        
    }else{
        
        jsonString = [[NSString alloc]initWithData:jsonData encoding:NSUTF8StringEncoding];
        
    }
    
    NSMutableString *mutStr = [NSMutableString stringWithString:jsonString];
    
    //    NSRange range = {0,jsonString.length};
    
    NSCharacterSet *doNotWant = [NSCharacterSet characterSetWithCharactersInString:@"[]{}（#%-*+=_）\\|~(＜＞$%^&*)_+ "];
    NSString * hmutStr = [[mutStr componentsSeparatedByCharactersInSet: doNotWant]componentsJoinedByString: @""];
    
    DDLogDebug(@"humStr is %@",hmutStr);
    
    return hmutStr;
}

#pragma mark - 去除json字符串中包含制表符
+(NSString *)removeUnescapedCharacter:(NSString *)inputStr
{
    if (inputStr)
    {
        NSCharacterSet *controlChars = [NSCharacterSet controlCharacterSet];//获取那些特殊字符
        NSRange range = [inputStr rangeOfCharacterFromSet:controlChars];//寻找字符串中有没有这些特殊字符
        if (range.location != NSNotFound)
        {
            NSMutableString *mutable = [NSMutableString stringWithString:inputStr];
            while (range.location != NSNotFound)
            {
                [mutable deleteCharactersInRange:range];//去掉这些特殊字符
                range = [mutable rangeOfCharacterFromSet:controlChars];
            }
            return mutable;
        }
        return inputStr;
    }
    return inputStr;
}

#pragma mark - 去除json字符串中包含html标签
+ (NSString *)flattenHTML:(NSString *)html {
    
    
    __block NSString *heml1 = html ?: @"";
    dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
    dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
    
    dispatch_async(queue, ^{
        
        //  过滤html标签
        NSScanner *theScanner;
        NSString *text = nil;
        theScanner = [NSScanner scannerWithString:heml1];
        while ([theScanner isAtEnd] == NO) {
            // find start of tag
            [theScanner scanUpToString:@"<" intoString:NULL] ;
            // find end of tag
            [theScanner scanUpToString:@">" intoString:&text] ;
            // replace the found tag with a space
            //(you can filter multi-spaces out later if you wish)
            heml1 = [heml1 stringByReplacingOccurrencesOfString:
                     [NSString stringWithFormat:@"%@>", text] withString:@""];
        }
        //  过滤html中的\n\r\t换行空格等特殊符号
        NSMutableString *str1 = [NSMutableString stringWithString:heml1];
        for (int i = 0; i < str1.length; i++) {
            unichar c = [str1 characterAtIndex:i];
            NSRange range = NSMakeRange(i, 1);
            //  在这里添加要过滤的特殊符号
            if ( c == '\r' || c == '\n' || c == '\t'  || c == '\0' || c == '\b' || c == '\v') {
                [str1 deleteCharactersInRange:range];
                --i;
            }
        }
        heml1  = [NSString stringWithString:str1];
        
        dispatch_semaphore_signal(semaphore);
    });
    
    dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
    
    return heml1;
}


+(NSString *)stringByTrimmingWhitespaceAndNewlineStr:(NSString *)str{
    NSMutableString * mutableString = [[NSMutableString alloc] initWithString:str];
    
    NSRange  trimRange = [mutableString rangeOfString:@"(?:^\\s+)" options:NSRegularExpressionSearch];
    if(trimRange.location!=NSNotFound)
        [mutableString deleteCharactersInRange:trimRange];
    
    trimRange=[mutableString rangeOfString:@"(?:\\s+$)" options:NSRegularExpressionSearch];
    if(trimRange.location!=NSNotFound)
        [mutableString deleteCharactersInRange:trimRange];
    
    return mutableString;
}

+(NSAttributedString *)stringByTrimmingWhitespaceAndNewlineAttributedString:(NSAttributedString *)attributedStr{
    NSMutableAttributedString * attributedString = [[NSMutableAttributedString alloc] initWithAttributedString:attributedStr];
    
    [attributedString beginEditing];
    NSRange  trimRange = [attributedString.string rangeOfString:@"(?:^\\s+)" options:NSRegularExpressionSearch];
    if(trimRange.location!=NSNotFound)
        [attributedString deleteCharactersInRange:trimRange];
    
    trimRange=[attributedString.string rangeOfString:@"(?:\\s+$)" options:NSRegularExpressionSearch];
    if(trimRange.location!=NSNotFound)
        [attributedString deleteCharactersInRange:trimRange];
    
    [attributedString endEditing];
    
    return attributedString;
}


//去掉double后面多余的0
+(NSString *)changeFloat:(NSString *)stringFloat
{
    const char *floatChars = [stringFloat UTF8String];
    NSUInteger length = [stringFloat length];
    NSUInteger zeroLength = 0;
    int i = length - 1;
    for(; i>=0; i--)
    {
        if(floatChars[i] == '0'/*0x30*/)
        {
            zeroLength++;
        }
        else
        {
            if(floatChars[i] == '.')
                i--;
            break;
        }
        
    }
    NSString *returnString;
    if(i == -1)
    {
        returnString = @"0";
    }
    else
    {
        returnString = [stringFloat substringToIndex:i+1];
    }
    return returnString;
}

#pragma mark - 将url里面的参数转换成字典
//将url里面的参数转换成字典
+ (NSDictionary *)getParamsWithURL:(NSURL *)url {
    
    //query是？后面的参数及alarm_id=11529&itemseq=1&status=1
    //因为在链接里面编码了 所以要解码
    NSString *query = [CSDNTool URLDecodedString:url.query];
    
    
    //进行字符串的拆分，通过&来拆分，把每个参数分开
    NSArray *subArray = [query componentsSeparatedByString:@"&"];
    //把subArray转换为字典
    //tempDic中存放一个URL中转换的键值对
    NSMutableDictionary *tempDic = [NSMutableDictionary dictionary];
    
    for (int i = 0 ; i < subArray.count ; i++) {
        //通过“=”拆分键和值
        NSArray *dicArray = [subArray[i] componentsSeparatedByString:@"="]
        ;
        if (dicArray.count == 2)
        {
            //给字典加入元素,=前面为key，后面为value
            [tempDic setObject:dicArray[1] forKey:dicArray[0]];
        }
    }
    //返回转换后的字典
    return tempDic ;
}

/**
 获取url的所有参数
 @param url 需要提取参数的url
 @return NSDictionary
 */
+(NSDictionary *)parameterWithURL:(NSURL *)url {
    if (!url) {
        return nil;
    }
    NSMutableDictionary *parm = [[NSMutableDictionary alloc]init];
    
    //传入url创建url组件类
    NSURLComponents *urlComponents = [[NSURLComponents alloc] initWithString:url.absoluteString];
    DDLogDebug(@"%@",urlComponents.queryItems);
    //回调遍历所有参数，添加入字典
    [urlComponents.queryItems enumerateObjectsUsingBlock:^(NSURLQueryItem * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) {
        if (obj.value && obj.name)
        {
            [parm setObject:obj.value forKey:obj.name];
        }
    }];
    
    return parm;
}


+ (NSString *)keyValueStringWithDict:(NSDictionary *)dict
{
    if (dict == nil) {
        return nil;
    }
    NSMutableString *string = [NSMutableString stringWithString:@"?"];
    [dict enumerateKeysAndObjectsUsingBlock:^(id key, id obj, BOOL *stop) {
        [string appendFormat:@"%@=%@&",key,obj];
    }];
    
    if ([string rangeOfString:@"&"].length) {
        [string deleteCharactersInRange:NSMakeRange(string.length - 1, 1)];
    }
    
    return string;
}

+(NSDictionary *)dictionaryWithUrlString:(NSString *)urlStr
{
    if (urlStr && urlStr.length && [urlStr rangeOfString:@"?"].length == 1) {
        NSArray *array = [urlStr componentsSeparatedByString:@"?"];
        if (array && array.count == 2) {
            NSString *paramsStr = array[1];
            if (paramsStr.length) {
                NSMutableDictionary *paramsDict = [NSMutableDictionary dictionary];
                NSArray *paramArray = [paramsStr componentsSeparatedByString:@"&"];
                for (NSString *param in paramArray) {
                    if (param && param.length) {
                        NSArray *parArr = [param componentsSeparatedByString:@"="];
                        if (parArr.count == 2) {
                            [paramsDict setObject:parArr[1] forKey:parArr[0]];
                        }
                    }
                }
                return paramsDict;
            }else{
                return nil;
            }
        }
        else{
            return nil;
        }
    }else{
        return nil;
    }
}

/**
 
 获取url中的参数并返回
 
 @param urlString 带参数的url
 @return @[NSString:无参数url, NSDictionary:参数字典]
 
 */

+ (NSArray*)getParamsWithUrlString:(NSString*)urlString {
    if(urlString.length==0) {
        DDLogDebug(@"链接为空！");
        return @[@"",@{}];
    }
    
    //先截取问号
    NSArray*allElements = [urlString componentsSeparatedByString:@"?"];
    NSMutableDictionary *params = [NSMutableDictionary dictionary];//待set的参数字典
    if(allElements.count==2) {
        //有参数或者?后面为空
        NSString*myUrlString = allElements[0];
        NSString*paramsString = allElements[1];
        //获取参数对
        NSArray*paramsArray = [paramsString componentsSeparatedByString:@"&"];
        if(paramsArray.count>=2) {
            
            for(NSInteger i =0; i < paramsArray.count; i++) {
                
                NSString*singleParamString = paramsArray[i];
                NSArray*singleParamSet = [singleParamString componentsSeparatedByString:@"="];
                if(singleParamSet.count==2) {
                    NSString*key = singleParamSet[0];
                    NSString*value = singleParamSet[1];
                    
                    if(key.length>0|| value.length>0) {
                        [params setObject:value.length>0?value:@""forKey:key.length>0?key:@""];
                    }
                    
                }
                
            }
            
        }else if(paramsArray.count==1) {
            //无 &。url只有?后一个参数
            NSString*singleParamString = paramsArray[0];
            NSArray*singleParamSet = [singleParamString componentsSeparatedByString:@"="];
            if(singleParamSet.count==2) {
                
                NSString*key = singleParamSet[0];
                NSString*value = singleParamSet[1];
                
                if(key.length>0|| value.length>0) {
                    
                    [params setObject:value.length>0?value:@""forKey:key.length>0?key:@""];
                }
                
            }else{
                //问号后面啥也没有 xxxx?  无需处理
            }
        }
        //整合url及参数
        return@[myUrlString,params];
        
    }else if(allElements.count>2) {
        DDLogDebug(@"链接不合法！链接包含多个\"?\"");
        return @[@"",@{}];
    }else{
        DDLogDebug(@"链接不包含参数！");
        return@[urlString,@{}];
    }
}

#pragma mark - 获取iPhone 机型
//获取iPhone 机型
// 获取设备型号然后手动转化为对应名称
+ (NSString *)getDeviceName
{
    struct utsname systemInfo;
    uname(&systemInfo);
    NSString *deviceString = [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding];
    
    if ([deviceString isEqualToString:@"iPhone3,1"])    return @"iPhone 4";
    if ([deviceString isEqualToString:@"iPhone3,2"])    return @"iPhone 4";
    if ([deviceString isEqualToString:@"iPhone3,3"])    return @"iPhone 4";
    if ([deviceString isEqualToString:@"iPhone4,1"])    return @"iPhone 4S";
    if ([deviceString isEqualToString:@"iPhone5,1"])    return @"iPhone 5";
    if ([deviceString isEqualToString:@"iPhone5,2"])    return @"iPhone 5 (GSM+CDMA)";
    if ([deviceString isEqualToString:@"iPhone5,3"])    return @"iPhone 5c (GSM)";
    if ([deviceString isEqualToString:@"iPhone5,4"])    return @"iPhone 5c (GSM+CDMA)";
    if ([deviceString isEqualToString:@"iPhone6,1"])    return @"iPhone 5s (GSM)";
    if ([deviceString isEqualToString:@"iPhone6,2"])    return @"iPhone 5s (GSM+CDMA)";
    if ([deviceString isEqualToString:@"iPhone7,1"])    return @"iPhone 6 Plus";
    if ([deviceString isEqualToString:@"iPhone7,2"])    return @"iPhone 6";
    if ([deviceString isEqualToString:@"iPhone8,1"])    return @"iPhone 6s";
    if ([deviceString isEqualToString:@"iPhone8,2"])    return @"iPhone 6s Plus";
    if ([deviceString isEqualToString:@"iPhone8,4"])    return @"iPhone SE";
    // 日行两款手机型号均为日本独占，可能使用索尼FeliCa支付方案而不是苹果支付
    //    if ([deviceString isEqualToString:@"iPhone9,1"])    return @"国行、日版、港行iPhone 7";
    //    if ([deviceString isEqualToString:@"iPhone9,2"])    return @"港行、国行iPhone 7 Plus";
    //    if ([deviceString isEqualToString:@"iPhone9,3"])    return @"美版、台版iPhone 7";
    //    if ([deviceString isEqualToString:@"iPhone9,4"])    return @"美版、台版iPhone 7 Plus";
    //    if ([deviceString isEqualToString:@"iPhone10,1"])   return @"国行(A1863)、日行(A1906)iPhone 8";
    //    if ([deviceString isEqualToString:@"iPhone10,4"])   return @"美版(Global/A1905)iPhone 8";
    //    if ([deviceString isEqualToString:@"iPhone10,2"])   return @"国行(A1864)、日行(A1898)iPhone 8 Plus";
    //    if ([deviceString isEqualToString:@"iPhone10,5"])   return @"美版(Global/A1897)iPhone 8 Plus";
    //    if ([deviceString isEqualToString:@"iPhone10,3"])   return @"国行(A1865)、日行(A1902)iPhone X";
    //    if ([deviceString isEqualToString:@"iPhone10,6"])   return @"美版(Global/A1901)iPhone X";
    if ([deviceString isEqualToString:@"iPhone9,1"])    return @"iPhone 7";
    if ([deviceString isEqualToString:@"iPhone9,2"])    return @"iPhone 7 Plus";
    if ([deviceString isEqualToString:@"iPhone9,3"])    return @"iPhone 7";
    if ([deviceString isEqualToString:@"iPhone9,4"])    return @"iPhone 7 Plus";
    if ([deviceString isEqualToString:@"iPhone10,1"])   return @"iPhone 8";
    if ([deviceString isEqualToString:@"iPhone10,4"])   return @"iPhone 8";
    if ([deviceString isEqualToString:@"iPhone10,2"])   return @"iPhone 8 Plus";
    if ([deviceString isEqualToString:@"iPhone10,5"])   return @"iPhone 8 Plus";
    if ([deviceString isEqualToString:@"iPhone10,3"])   return @"iPhone X";
    if ([deviceString isEqualToString:@"iPhone10,6"])   return @"iPhone X";
    if ([deviceString isEqualToString:@"iPhone11,2"])   return @"iPhone XS";
    if ([deviceString isEqualToString:@"iPhone11,4"])   return @"iPhone XS Max";
    if ([deviceString isEqualToString:@"iPhone11,6"])   return @"iPhone XS Max";
    if ([deviceString isEqualToString:@"iPhone11,8"])   return @"iPhone XR";
    if ([deviceString isEqualToString:@"iPhone12,1"])   return @"iPhone 11";
    if ([deviceString isEqualToString:@"iPhone12,3"])   return @"iPhone 11 Pro";
    if ([deviceString isEqualToString:@"iPhone12,5"])   return @"iPhone 11 Pro Max";
    
    if ([deviceString isEqualToString:@"iPod1,1"])      return @"iPod Touch 1G";
    if ([deviceString isEqualToString:@"iPod2,1"])      return @"iPod Touch 2G";
    if ([deviceString isEqualToString:@"iPod3,1"])      return @"iPod Touch 3G";
    if ([deviceString isEqualToString:@"iPod4,1"])      return @"iPod Touch 4G";
    if ([deviceString isEqualToString:@"iPod5,1"])      return @"iPod Touch (5 Gen)";
    
    if ([deviceString isEqualToString:@"iPad1,1"])      return @"iPad";
    if ([deviceString isEqualToString:@"iPad1,2"])      return @"iPad 3G";
    if ([deviceString isEqualToString:@"iPad2,1"])      return @"iPad 2 (WiFi)";
    if ([deviceString isEqualToString:@"iPad2,2"])      return @"iPad 2";
    if ([deviceString isEqualToString:@"iPad2,3"])      return @"iPad 2 (CDMA)";
    if ([deviceString isEqualToString:@"iPad2,4"])      return @"iPad 2";
    if ([deviceString isEqualToString:@"iPad2,5"])      return @"iPad Mini (WiFi)";
    if ([deviceString isEqualToString:@"iPad2,6"])      return @"iPad Mini";
    if ([deviceString isEqualToString:@"iPad2,7"])      return @"iPad Mini (GSM+CDMA)";
    if ([deviceString isEqualToString:@"iPad3,1"])      return @"iPad 3 (WiFi)";
    if ([deviceString isEqualToString:@"iPad3,2"])      return @"iPad 3 (GSM+CDMA)";
    if ([deviceString isEqualToString:@"iPad3,3"])      return @"iPad 3";
    if ([deviceString isEqualToString:@"iPad3,4"])      return @"iPad 4 (WiFi)";
    if ([deviceString isEqualToString:@"iPad3,5"])      return @"iPad 4";
    if ([deviceString isEqualToString:@"iPad3,6"])      return @"iPad 4 (GSM+CDMA)";
    if ([deviceString isEqualToString:@"iPad4,1"])      return @"iPad Air (WiFi)";
    if ([deviceString isEqualToString:@"iPad4,2"])      return @"iPad Air (Cellular)";
    if ([deviceString isEqualToString:@"iPad4,4"])      return @"iPad Mini 2 (WiFi)";
    if ([deviceString isEqualToString:@"iPad4,5"])      return @"iPad Mini 2 (Cellular)";
    if ([deviceString isEqualToString:@"iPad4,6"])      return @"iPad Mini 2";
    if ([deviceString isEqualToString:@"iPad4,7"])      return @"iPad Mini 3";
    if ([deviceString isEqualToString:@"iPad4,8"])      return @"iPad Mini 3";
    if ([deviceString isEqualToString:@"iPad4,9"])      return @"iPad Mini 3";
    if ([deviceString isEqualToString:@"iPad5,1"])      return @"iPad Mini 4 (WiFi)";
    if ([deviceString isEqualToString:@"iPad5,2"])      return @"iPad Mini 4 (LTE)";
    if ([deviceString isEqualToString:@"iPad5,3"])      return @"iPad Air 2";
    if ([deviceString isEqualToString:@"iPad5,4"])      return @"iPad Air 2";
    if ([deviceString isEqualToString:@"iPad6,3"])      return @"iPad Pro 9.7";
    if ([deviceString isEqualToString:@"iPad6,4"])      return @"iPad Pro 9.7";
    if ([deviceString isEqualToString:@"iPad6,7"])      return @"iPad Pro 12.9";
    if ([deviceString isEqualToString:@"iPad6,8"])      return @"iPad Pro 12.9";
    if ([deviceString isEqualToString:@"iPad6,11"])    return @"iPad 5 (WiFi)";
    if ([deviceString isEqualToString:@"iPad6,12"])    return @"iPad 5 (Cellular)";
    if ([deviceString isEqualToString:@"iPad7,1"])     return @"iPad Pro 12.9 inch 2nd gen (WiFi)";
    if ([deviceString isEqualToString:@"iPad7,2"])     return @"iPad Pro 12.9 inch 2nd gen (Cellular)";
    if ([deviceString isEqualToString:@"iPad7,3"])     return @"iPad Pro 10.5 inch (WiFi)";
    if ([deviceString isEqualToString:@"iPad7,4"])     return @"iPad Pro 10.5 inch (Cellular)";
    if ([deviceString isEqualToString:@"iPad7,5"])     return @"iPad 2018";
    if ([deviceString isEqualToString:@"iPad8,1"])     return @"iPad Pro 11-inch";
    if ([deviceString isEqualToString:@"iPad8,2"])     return @"iPad Pro 11-inch";
    if ([deviceString isEqualToString:@"iPad8,3"])     return @"iPad Pro 11-inch";
    if ([deviceString isEqualToString:@"iPad8,4"])     return @"iPad Pro 11-inch";
    if ([deviceString isEqualToString:@"iPad8,5"])     return @"iPad Pro 12.9-inch";
    if ([deviceString isEqualToString:@"iPad8,6"])     return @"iPad Pro 12.9-inch";
    if ([deviceString isEqualToString:@"iPad8,7"])     return @"iPad Pro 12.9-inch";
    if ([deviceString isEqualToString:@"iPad8,8"])     return @"iPad Pro 12.9-inch";
    
    if ([deviceString isEqualToString:@"iPad11,1"])     return @"iPad Mini 5";
    if ([deviceString isEqualToString:@"iPad11,2"])     return @"iPad Mini 5";
    if ([deviceString isEqualToString:@"iPad11,3"])     return @"iPad Air 3";
    if ([deviceString isEqualToString:@"iPad11,4"])     return @"iPad Air 4";
    
    if ([deviceString isEqualToString:@"AppleTV2,1"])    return @"Apple TV 2";
    if ([deviceString isEqualToString:@"AppleTV3,1"])    return @"Apple TV 3";
    if ([deviceString isEqualToString:@"AppleTV3,2"])    return @"Apple TV 3";
    if ([deviceString isEqualToString:@"AppleTV5,3"])    return @"Apple TV 4";
    
    if ([deviceString isEqualToString:@"i386"])         return @"Simulator";
    if ([deviceString isEqualToString:@"x86_64"])       return @"Simulator";
    
    return deviceString;
}

/**
 *  设备版本
 *
 *  @return
 */
+ (NSString*)deviceVersion
{
    // 需要#import "sys/utsname.h"
    struct utsname systemInfo;
    uname(&systemInfo);
    NSString *deviceString = [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding];
    return deviceString;
}

/**
 *  清理缓存
 */
+(void)cleanCache:(cleanCacheBlock)block
{
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        [self cleanCaches:[self getCachesPath]];
        
        //清除论坛页面保存的图片url
        NSUserDefaults * defs = [NSUserDefaults standardUserDefaults];
        NSDictionary * dict = [defs dictionaryRepresentation];
        for (id key in dict)
        {
            if ([(NSString *)key containsString:@"https://"]||[(NSString *)key containsString:@"http://"])
            {
                [defs removeObjectForKey:key];
            }
        }
        [defs synchronize];
        
        
        //返回主线程
        dispatch_async(dispatch_get_main_queue(), ^{
            block();
        });
    });
    
}


// 获取Caches目录路径
+ (NSString *)getCachesPath
{
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask,YES);
    NSString *cachesDir = [paths lastObject];
    return cachesDir;
}

+ (CGFloat)folderSizeAtPath:(NSString *)path
{
//    NSFileManager *manager = [NSFileManager defaultManager];
//    CGFloat size = 0;
//    if ([manager fileExistsAtPath:path]) {
//        // 目录下的文件计算大小
//        NSArray *childrenFile = [manager subpathsAtPath:path];
//        for (NSString *fileName in childrenFile) {
//            NSString *absolutePath = [path stringByAppendingPathComponent:fileName];
//            size += [manager attributesOfItemAtPath:absolutePath error:nil].fileSize;
//        }
//        //YYWebImage的缓存计算
//        size += [YYWebImageManager sharedManager].cache.memoryCache.totalCount /1024.0/1024.0;
//        size += [[SDImageCache sharedImageCache] totalDiskSize]/1024.0/1024.0;        // 将大小转化为M,size单位b,转，KB,MB除以两次1024
//        return size / 1024.0 / 1024.0;
//    }
//    return 0;
    //只计算图片缓存
     CGFloat size = 0;
    //YYWebImage的缓存计算
    size += ([YYWebImageManager sharedManager].cache.diskCache.totalCount != -1?:0);
    size += [[SDImageCache sharedImageCache] totalDiskSize];         // 将大小转化为M,size单位b,转，KB,MB除以两次1024
    return (size/1024.0/1024.0);
}

+ (void)cleanCaches:(NSString *)path
{
    NSFileManager *fileManager = [NSFileManager defaultManager];
    if ([fileManager fileExistsAtPath:path]) {
        NSArray *childrenFiles = [fileManager subpathsAtPath:path];
        for (NSString *fileName in childrenFiles) {
            // 拼接路径
            NSString *absolutePath = [path stringByAppendingPathComponent:fileName];
            // 将文件删除
            [fileManager removeItemAtPath:absolutePath error:nil];
        }
    }
    //YYWebImage的清除功能
    // 清空缓存
    [[YYWebImageManager sharedManager].cache.memoryCache removeAllObjects];
    [[YYWebImageManager sharedManager].cache.diskCache removeAllObjects];
    //SDWebImage
    [[SDImageCache sharedImageCache] clearDiskOnCompletion:nil];
    [[SDImageCache sharedImageCache] clearMemory];
    dispatch_async(dispatch_get_main_queue(), ^{
        //清空 WebView 缓存
        [self removeWebCache];
    });
    
}

//清空 WKWebView 缓存
+ (void)removeWebCache{
    if ([[UIDevice currentDevice].systemVersion floatValue] >= 9.0) {
        NSSet *websiteDataTypes= [NSSet setWithArray:@[
                                                       WKWebsiteDataTypeDiskCache,
                                                       //WKWebsiteDataTypeOfflineWebApplication
                                                       WKWebsiteDataTypeMemoryCache,
                                                       //WKWebsiteDataTypeLocal
                                                       WKWebsiteDataTypeCookies,
                                                       //WKWebsiteDataTypeSessionStorage,
                                                       //WKWebsiteDataTypeIndexedDBDatabases,
                                                       //WKWebsiteDataTypeWebSQLDatabases
                                                       ]];
        
        // All kinds of data
        //NSSet *websiteDataTypes = [WKWebsiteDataStore allWebsiteDataTypes];
        NSDate *dateFrom = [NSDate dateWithTimeIntervalSince1970:0];
        [[WKWebsiteDataStore defaultDataStore] removeDataOfTypes:websiteDataTypes modifiedSince:dateFrom completionHandler:^{
            
        }];
        [[NSURLCache sharedURLCache] removeAllCachedResponses];
        
    }
}

//清空 WKWebView cookie
+ (void)removeWebCookie{
    if (@available(iOS 9, *)){
        // 以www.csdn.net为例，是否包含csdn.net
        NSString *displayName = @"csdn.net";
        WKWebsiteDataStore *dataStore = [WKWebsiteDataStore defaultDataStore];
        [dataStore fetchDataRecordsOfTypes:[WKWebsiteDataStore allWebsiteDataTypes] completionHandler:^(NSArray<WKWebsiteDataRecord *> * __nonnull records) {
            for (WKWebsiteDataRecord *record  in records){
                if ([displayName containsString:record.displayName]){
                    [[WKWebsiteDataStore defaultDataStore] removeDataOfTypes:record.dataTypes forDataRecords:@[record] completionHandler:^{
                        NSLog(@"Cookies for %@ deleted successfully",record.displayName);
                    }];
                }
            }
        }];
        NSString *libraryPath = [NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES) objectAtIndex:0];
        NSString *cookiesFolderPath = [libraryPath stringByAppendingString:@"/Cookies"];
        NSError *errors;
        [[NSFileManager defaultManager] removeItemAtPath:cookiesFolderPath error:&errors];
        
        //清除cookie方法
        NSArray * cookArray = [[NSHTTPCookieStorage sharedHTTPCookieStorage] cookies];
        for (NSHTTPCookie*cookie in cookArray) {
            [[NSHTTPCookieStorage sharedHTTPCookieStorage] deleteCookie:cookie];
        }
    }
}

/**
 *  判断是否是url
 */
+ (BOOL)isUrlAddress:(NSString*)url

{
    NSError *error = nil;
    NSDataDetector *detector = [NSDataDetector dataDetectorWithTypes:NSTextCheckingTypeLink
                                                               error:&error];
    NSArray *matches = [detector matchesInString:url
                                         options:kNilOptions
                                           range:NSMakeRange(0, url.length)];
    
    if (matches.count == 1) {
        NSTextCheckingResult *result = matches.firstObject;
        if (result.range.location == 0) {
            return YES;
        } else {
            return NO;
        }
    } else {
        return NO;
    }
}

/**
 获取WebView截屏
 
 @param webView webView
 @return 图片
 */
+ (UIImage *)imageForWebView:(WKWebView *)webView
{
    // 1.获取WebView的宽高
    CGSize boundsSize = webView.bounds.size;
    CGFloat boundsWidth = boundsSize.width;
    CGFloat boundsHeight = boundsSize.height;
    
    // 2.获取contentSize
    CGSize contentSize = webView.scrollView.contentSize;
    CGFloat contentHeight = contentSize.height;
    // 3.保存原始偏移量，便于截图后复位
    CGPoint offset = webView.scrollView.contentOffset;
    // 4.设置最初的偏移量为(0,0);
    [webView.scrollView setContentOffset:CGPointMake(0, 0)];
    
    NSMutableArray *images = [NSMutableArray array];
    while (contentHeight > 0) {
        // 5.获取CGContext 5.获取CGContext
        UIGraphicsBeginImageContextWithOptions(boundsSize, NO, 0.0);
        CGContextRef ctx = UIGraphicsGetCurrentContext();
        // 6.渲染要截取的区域
        [webView.layer renderInContext:ctx];
        UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
        UIGraphicsEndImageContext();
        // 7.截取的图片保存起来
        [images addObject:image];
        
        CGFloat offsetY = webView.scrollView.contentOffset.y;
        [webView.scrollView setContentOffset:CGPointMake(0, offsetY + boundsHeight)];
        contentHeight -= boundsHeight;
    }
    // 8 webView 恢复到之前的显示区域
    [webView.scrollView setContentOffset:offset];
    CGFloat scale = [UIScreen mainScreen].scale;
    CGSize imageSize = CGSizeMake(contentSize.width * scale,
                                  contentSize.height * scale);
    // 9.根据设备的分辨率重新绘制、拼接成完整清晰图片
    UIGraphicsBeginImageContext(imageSize);
    [images enumerateObjectsUsingBlock:^(UIImage *image, NSUInteger idx, BOOL *stop) {
        [image drawInRect:CGRectMake(0,scale * boundsHeight * idx,scale * boundsWidth,scale * boundsHeight)];
    }];
    UIImage *fullImage = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    
    return fullImage;
}

//获取当前手机连接Wifi的名称 SSID
+ (NSString *)getWifiName
{
    NSString *ssid = @"Not Found";
    CFArrayRef myArray = CNCopySupportedInterfaces();
    if (myArray != nil) {
        CFDictionaryRef myDict = CNCopyCurrentNetworkInfo(CFArrayGetValueAtIndex(myArray, 0));
        if (myDict != nil) {
            NSDictionary *dict = (NSDictionary*)CFBridgingRelease(myDict);
            ssid = [dict valueForKey:@"SSID"];
        }
    }
    return ssid;
}

//获取当前手机连接Wifi的mac地址
+ (NSString *)getWifiMacAddress
{
    NSString *macIp = @"Not Found";
    CFArrayRef myArray = CNCopySupportedInterfaces();
    if (myArray != nil) {
        CFDictionaryRef myDict = CNCopyCurrentNetworkInfo(CFArrayGetValueAtIndex(myArray, 0));
        if (myDict != nil) {
            NSDictionary *dict = (NSDictionary*)CFBridgingRelease(myDict);
            macIp = [dict valueForKey:@"BSSID"];
        }
    }
    return macIp;
}

#pragma mark - 获取设备当前网络IP地址
+ (NSString *)getIPAddress:(BOOL)preferIPv4
{
    NSArray *searchArray = preferIPv4 ?
    @[ IOS_VPN @"/" IP_ADDR_IPv4, IOS_VPN @"/" IP_ADDR_IPv6, IOS_WIFI @"/" IP_ADDR_IPv4, IOS_WIFI @"/" IP_ADDR_IPv6, IOS_CELLULAR @"/" IP_ADDR_IPv4, IOS_CELLULAR @"/" IP_ADDR_IPv6 ] :
    @[ IOS_VPN @"/" IP_ADDR_IPv6, IOS_VPN @"/" IP_ADDR_IPv4, IOS_WIFI @"/" IP_ADDR_IPv6, IOS_WIFI @"/" IP_ADDR_IPv4, IOS_CELLULAR @"/" IP_ADDR_IPv6, IOS_CELLULAR @"/" IP_ADDR_IPv4 ] ;
    
    NSDictionary *addresses = [self getIPAddresses];
    DDLogDebug(@"addresses: %@", addresses);
    
    __block NSString *address;
    [searchArray enumerateObjectsUsingBlock:^(NSString *key, NSUInteger idx, BOOL *stop)
     {
        address = addresses[key];
        //筛选出IP地址格式
        if([self isValidatIP:address]) *stop = YES;
    } ];
    return address ? address : @"0.0.0.0";
}

+ (BOOL)isValidatIP:(NSString *)ipAddress {
    if (ipAddress.length == 0) {
        return NO;
    }
    NSString *urlRegEx = @"^([01]?\\d\\d?|2[0-4]\\d|25[0-5])\\."
    "([01]?\\d\\d?|2[0-4]\\d|25[0-5])\\."
    "([01]?\\d\\d?|2[0-4]\\d|25[0-5])\\."
    "([01]?\\d\\d?|2[0-4]\\d|25[0-5])$";
    
    NSError *error;
    NSRegularExpression *regex = [NSRegularExpression regularExpressionWithPattern:urlRegEx options:0 error:&error];
    
    if (regex != nil) {
        NSTextCheckingResult *firstMatch=[regex firstMatchInString:ipAddress options:0 range:NSMakeRange(0, [ipAddress length])];
        
        if (firstMatch) {
            NSRange resultRange = [firstMatch rangeAtIndex:0];
            NSString *result=[ipAddress substringWithRange:resultRange];
            //输出结果
            DDLogDebug(@"%@",result);
            return YES;
        }
    }
    return NO;
}

// Get IP Address
- (NSString *)getWIFIIPAddress
{
    NSString *address = @"error";
    struct ifaddrs *interfaces = NULL;
    struct ifaddrs *temp_addr = NULL;
    int success = 0;
    // retrieve the current interfaces - returns 0 on success
    success = getifaddrs(&interfaces);
    if (success == 0) {
        // Loop through linked list of interfaces
        temp_addr = interfaces;
        while(temp_addr != NULL) {
            if(temp_addr->ifa_addr->sa_family == AF_INET) {
                // Check if interface is en0 which is the wifi connection on the iPhone
                if([[NSString stringWithUTF8String:temp_addr->ifa_name] isEqualToString:@"en0"]) {
                    // Get NSString from C String
                    address = [NSString stringWithUTF8String:inet_ntoa(((struct sockaddr_in *)temp_addr->ifa_addr)->sin_addr)];
                }
            }
            temp_addr = temp_addr->ifa_next;
        }
    }
    // Free memory
    freeifaddrs(interfaces);
    return address;
    
}

+ (NSDictionary *)getIPAddresses
{
    NSMutableDictionary *addresses = [NSMutableDictionary dictionaryWithCapacity:8];
    
    // retrieve the current interfaces - returns 0 on success
    struct ifaddrs *interfaces;
    if(!getifaddrs(&interfaces)) {
        // Loop through linked list of interfaces
        struct ifaddrs *interface;
        for(interface=interfaces; interface; interface=interface->ifa_next) {
            if(!(interface->ifa_flags & IFF_UP) /* || (interface->ifa_flags & IFF_LOOPBACK) */ ) {
                continue; // deeply nested code harder to read
            }
            const struct sockaddr_in *addr = (const struct sockaddr_in*)interface->ifa_addr;
            char addrBuf[ MAX(INET_ADDRSTRLEN, INET6_ADDRSTRLEN) ];
            if(addr && (addr->sin_family==AF_INET || addr->sin_family==AF_INET6)) {
                NSString *name = [NSString stringWithUTF8String:interface->ifa_name];
                NSString *type;
                if(addr->sin_family == AF_INET) {
                    if(inet_ntop(AF_INET, &addr->sin_addr, addrBuf, INET_ADDRSTRLEN)) {
                        type = IP_ADDR_IPv4;
                    }
                } else {
                    const struct sockaddr_in6 *addr6 = (const struct sockaddr_in6*)interface->ifa_addr;
                    if(inet_ntop(AF_INET6, &addr6->sin6_addr, addrBuf, INET6_ADDRSTRLEN)) {
                        type = IP_ADDR_IPv6;
                    }
                }
                if(type) {
                    NSString *key = [NSString stringWithFormat:@"%@/%@", name, type];
                    addresses[key] = [NSString stringWithUTF8String:addrBuf];
                }
            }
        }
        // Free memory
        freeifaddrs(interfaces);
    }
    return [addresses count] ? addresses : nil;
}

//获取UserAgent
+(NSString *)getWebUserAgent
{
    UIApplicationState state = [UIApplication sharedApplication].applicationState;

    BOOL result = (state == UIApplicationStateBackground);
    if (result) {
        return [self getUserAgent];
    }
    return [[[UIWebView alloc] init] stringByEvaluatingJavaScriptFromString:@"navigator.userAgent"];
}

+(NSString *)getUserAgent
{
    return [NSString stringWithFormat:@"%@/%@ (%@; iOS %@; Scale/%0.2f)", [[NSBundle mainBundle] infoDictionary][(__bridge NSString *)kCFBundleExecutableKey] ?: [[NSBundle mainBundle] infoDictionary][(__bridge NSString *)kCFBundleIdentifierKey], [[NSBundle mainBundle] infoDictionary][@"CFBundleShortVersionString"] ?: [[NSBundle mainBundle] infoDictionary][(__bridge NSString *)kCFBundleVersionKey], [[UIDevice currentDevice] model], [[UIDevice currentDevice] systemVersion], [[UIScreen mainScreen] scale]];
}

+(NSString *)getMobileCountryCode
{
    NSString *mobileCountryCode = @"";
    CTTelephonyNetworkInfo *telephonyInfo = [[CTTelephonyNetworkInfo alloc] init];
    CTCarrier *carrier = [telephonyInfo subscriberCellularProvider];
    //    NSString *currentCountry=[carrier carrierName];
    mobileCountryCode = [NSString stringWithFormat:@"%@%@",[carrier mobileCountryCode],[carrier mobileNetworkCode]];
    //    NSLog(@"[carrier isoCountryCode]==%@,[carrier allowsVOIP]=%d,[carrier mobileCountryCode=%@,[carrier mobileNetworkCode]=%@---%@",[carrier isoCountryCode],[carrier allowsVOIP],[carrier mobileCountryCode],[carrier mobileNetworkCode],currentCountry);
    return mobileCountryCode;
}



/**
 随机数生成
 
 @param from
 @param to
 @return
 */
+(NSInteger)getRandomNumber:(NSInteger)from to:(NSInteger)to
{
    return (NSInteger)(from + (arc4random() % (to - from + 1)));
}

//获取当前时间 offsetTime 秒后的时间戳
+(NSString *)timeStampWithOffsetTime:(NSInteger)offsetTime
{
    NSDate* date = [NSDate dateWithTimeIntervalSinceNow:offsetTime];//获取当前时间 offsetTime 秒后的时间
    NSTimeInterval time =[date timeIntervalSince1970];//默认单位是秒，*1000单位为毫秒
    NSString *timeStampString = [NSString stringWithFormat:@"%.0f", time];
    return timeStampString;
}

//获取当前时间戳
+ (NSString *)currentTimeStampStr
{
    NSDate* date = [NSDate dateWithTimeIntervalSinceNow:0];//获取当前时间0秒后的时间
    NSTimeInterval time=[date timeIntervalSince1970]*1000;// *1000 是精确到毫秒，不乘就是精确到秒
    NSString *timeString = [NSString stringWithFormat:@"%.0f", time];
    return timeString;
}

+ (NSTimeInterval )currentTimeStamp{
    NSDate* date = [NSDate dateWithTimeIntervalSinceNow:0];//获取当前时间0秒后的时间
    NSTimeInterval time=[date timeIntervalSince1970];
    return time;
}

+ (NSTimeInterval )currentMeasureTimeStamp{
    NSDate* date = [NSDate dateWithTimeIntervalSinceNow:0];//获取当前时间0秒后的时间
    NSTimeInterval time=[date timeIntervalSince1970] * 1000;
    return time;
}


/**
 * 过滤标签
 */
+(NSString *)filterHTML:(NSString *)str
{
    NSScanner * scanner = [NSScanner scannerWithString:str];
    NSString * text = nil;
    while([scanner isAtEnd]==NO)
    {
        //找到标签的起始位置
        [scanner scanUpToString:@"<" intoString:nil];
        //找到标签的结束位置
        [scanner scanUpToString:@">" intoString:&text];
        //替换字符
        str  =  [str  stringByReplacingOccurrencesOfString:[NSString stringWithFormat:@"%@>",text] withString:@""];
    }
    return str;
}
+(NSString *)filterHTMLImage:(NSString *)str{
    NSScanner * scanner = [NSScanner scannerWithString:str];
    NSString * text = nil;
    while([scanner isAtEnd]==NO)
    {
        //找到标签的起始位置
        [scanner scanUpToString:@"<img" intoString:nil];
        //找到标签的结束位置
        [scanner scanUpToString:@">" intoString:&text];
        //替换字符
        str  =  [str  stringByReplacingOccurrencesOfString:[NSString stringWithFormat:@"%@>",text] withString:@"【图片】"];
    }
    return str;
}

+ (NSString *)filterHTMLTag:(NSString *)str {
    //替换字符
    str  =  [str  stringByReplacingOccurrencesOfString:@"&mdash;" withString:@"-"];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&ldquo;" withString:@"\""];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&rdquo;" withString:@"\""];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&nbsp;" withString:@" "];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&rsquo;" withString:@"’"];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&lsquo;" withString:@"‘"];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&middot;" withString:@"·"];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&quot;" withString:@"\""];
    str  =  [str  stringByReplacingOccurrencesOfString:@"&amp;" withString:@"&"];
    str  =  [str  stringByReplacingOccurrencesOfString:@"<strong>" withString:@""];
    str  =  [str  stringByReplacingOccurrencesOfString:@"</strong>" withString:@""];
    str  =  [str  stringByReplacingOccurrencesOfString:@"\n" withString:@" "];
    return str;
    
}


+ (NSString *)filterHTMLTags:(NSString *)htmlStr
{
    if (!htmlStr)
        
    {
        return @"";
    }
    htmlStr = [htmlStr stringByReplacingRegex:@"\\s" options:NSRegularExpressionCaseInsensitive withString:@""];
    htmlStr = [htmlStr stringByReplacingRegex:@".*<body[^<>]*>" options:NSRegularExpressionCaseInsensitive withString:@""];
    htmlStr = [htmlStr stringByReplacingRegex:@"</body>.*" options:NSRegularExpressionCaseInsensitive withString:@""];
    htmlStr = [htmlStr stringByReplacingRegex:@"<script[^<>]*>.*</script>" options:NSRegularExpressionCaseInsensitive withString:@""];
    htmlStr = [htmlStr stringByReplacingRegex:@"<style[^<>]*>.*</style>" options:NSRegularExpressionCaseInsensitive withString:@""];
    htmlStr = [htmlStr stringByReplacingRegex:@"<[^<>]*>" options:NSRegularExpressionCaseInsensitive withString:@""];
    return htmlStr.stringByTrim;
}

+ (NSString *)getCurrentLanguage
{
    NSArray  *languageList =  [[NSUserDefaults standardUserDefaults] objectForKey:@"AppleLanguages"] ;// 本机设置的语言列表
    DDLogDebug(@"languageList : %@", languageList);
    NSString *languageCode = [languageList  firstObject];// 当前设置的首选语言
    NSString *countryCode = [NSString stringWithFormat:@"-%@", [[NSLocale currentLocale] objectForKey:NSLocaleCountryCode]];
    if (languageCode) {
        languageCode = [languageCode stringByReplacingOccurrencesOfString:countryCode withString:@""];
    }
    return languageCode;
}

/**
 *  随机生成UUID
 *
 *  @return
 */
+ (NSString *)uuidString
{
    CFUUIDRef uuid_ref = CFUUIDCreate(NULL);
    CFStringRef uuid_string_ref= CFUUIDCreateString(NULL, uuid_ref);
    NSString *uuid = [NSString stringWithString:(__bridge NSString *)uuid_string_ref];
    CFRelease(uuid_ref);
    CFRelease(uuid_string_ref);
    return [uuid lowercaseString];
}

+(NSString *)getNeedSignStrFrom:(NSDictionary *)dict
{
    if (dict == nil) {
        return @"";
    }
    NSArray *arrPrimary = dict.allKeys;
    NSArray *arrKey = [arrPrimary sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2){
        NSComparisonResult result = [obj1 compare:obj2];
        return result==NSOrderedDescending;//NSOrderedAscending 倒序
    }];
    NSString*str =@"";
    for (NSString *s in arrKey) {
        id value = dict[s];
        if([value isKindOfClass:[NSDictionary class]]) {
            value = [self getNeedSignStrFrom:value];
        }
        if([str length] !=0) {
            
            str = [str stringByAppendingString:@"&"];
        }
        str = [str stringByAppendingFormat:@"%@=%@",s,value];
    }
    return str;
}


/**
 ASE256加密
 
 @param content
 @param key
 @param iv
 @return
 */
+ (NSString *)encrypyAES:(NSString *)content key:(NSString *)key iv:(NSString *)iv{
    
    NSData *contentData = [content dataUsingEncoding:NSUTF8StringEncoding];
    NSUInteger dataLength = contentData.length;
    
    // 为结束符'\\0' +1
    char keyPtr[kCCKeySizeAES128 + 1];
    memset(keyPtr, 0, sizeof(keyPtr));
    [key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];
    
    size_t encryptSize = dataLength + kCCBlockSizeAES128;
    void *encryptedBytes = malloc(encryptSize);
    size_t actualOutSize = 0;
    
    NSData *initVector = [iv dataUsingEncoding:NSUTF8StringEncoding];
    
    CCCryptorStatus cryptStatus = CCCrypt(kCCEncrypt,
                                          kCCAlgorithmAES128,
                                          kCCOptionPKCS7Padding /*| kCCOptionECBMode*/, // 加密模式
                                          keyPtr,
                                          kCCKeySizeAES128,
                                          initVector.bytes,
                                          contentData.bytes,
                                          dataLength,
                                          encryptedBytes,
                                          encryptSize,
                                          &actualOutSize);
    
    if (cryptStatus == kCCSuccess) {
        // 对加密后的数据进行 base64 编码
        return [[NSData dataWithBytesNoCopy:encryptedBytes length:actualOutSize] base64EncodedStringWithOptions:NSDataBase64EncodingEndLineWithLineFeed];
    }
    free(encryptedBytes);
    return nil;
}

/**
 ASE256解密
 
 @param content
 @param key
 @param iv
 @return
 */
+ (NSString *)descryptAES:(NSString *)content key:(NSString *)key iv:(NSString *)iv {//
    // 把 base64 String 转换成 NSData
    NSData *contentData = [[NSData alloc] initWithBase64EncodedString:content options:NSDataBase64DecodingIgnoreUnknownCharacters];
    NSUInteger dataLength = contentData.length;
    
    char keyPtr[kCCKeySizeAES128 + 1];
    memset(keyPtr, 0, sizeof(keyPtr));
    [key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];
    
    size_t decryptSize = dataLength + kCCBlockSizeAES128;
    void *decryptedBytes = malloc(decryptSize);
    size_t actualOutSize = 0;
    
    NSData *initVector = [iv dataUsingEncoding:NSUTF8StringEncoding];
    
    CCCryptorStatus cryptStatus = CCCrypt(kCCDecrypt,
                                          kCCAlgorithmAES,
                                          kCCOptionPKCS7Padding /*| kCCOptionECBMode*/, // 加密模式
                                          keyPtr,
                                          kCCKeySizeAES128,
                                          initVector.bytes,
                                          contentData.bytes,
                                          dataLength,
                                          decryptedBytes,
                                          decryptSize,
                                          &actualOutSize);
    
    if (cryptStatus == kCCSuccess) {
        return [[NSString alloc] initWithData:[NSData dataWithBytesNoCopy:decryptedBytes length:actualOutSize] encoding:NSUTF8StringEncoding];
    }
    
    free(decryptedBytes);
    return nil;
}


/**
 设置view指定位置的边框
 
 @param originalView   原view
 @param color          边框颜色
 @param borderWidth    边框宽度
 @param borderType     边框类型 例子: UIBorderSideTypeTop|UIBorderSideTypeBottom
 @return  view
 */
+ (UIView *)borderForView:(UIView *)originalView color:(UIColor *)color borderWidth:(CGFloat)borderWidth borderType:(UIBorderSideType)borderType
{
    
    if (borderType == UIBorderSideTypeAll) {
        originalView.layer.borderWidth = borderWidth;
        originalView.layer.borderColor = color.CGColor;
        return originalView;
    }
    
    /// 线的路径
    UIBezierPath * bezierPath = [UIBezierPath bezierPath];
    
    /// 左侧
    if (borderType & UIBorderSideTypeLeft) {
        /// 左侧线路径
        [bezierPath moveToPoint:CGPointMake(0.0f, originalView.frame.size.height)];
        [bezierPath addLineToPoint:CGPointMake(0.0f, 0.0f)];
    }
    
    /// 右侧
    if (borderType & UIBorderSideTypeRight) {
        /// 右侧线路径
        [bezierPath moveToPoint:CGPointMake(originalView.frame.size.width, 0.0f)];
        [bezierPath addLineToPoint:CGPointMake( originalView.frame.size.width, originalView.frame.size.height)];
    }
    
    /// top
    if (borderType & UIBorderSideTypeTop) {
        /// top线路径
        [bezierPath moveToPoint:CGPointMake(0.0f, 0.0f)];
        [bezierPath addLineToPoint:CGPointMake(originalView.frame.size.width, 0.0f)];
    }
    
    /// bottom
    if (borderType & UIBorderSideTypeBottom) {
        /// bottom线路径
        [bezierPath moveToPoint:CGPointMake(0.0f, originalView.frame.size.height)];
        [bezierPath addLineToPoint:CGPointMake( originalView.frame.size.width, originalView.frame.size.height)];
    }
    
    CAShapeLayer * shapeLayer = [CAShapeLayer layer];
    shapeLayer.strokeColor = color.CGColor;
    shapeLayer.fillColor  = [UIColor clearColor].CGColor;
    /// 添加路径
    shapeLayer.path = bezierPath.CGPath;
    /// 线宽度
    shapeLayer.lineWidth = borderWidth;
    
    [originalView.layer addSublayer:shapeLayer];
    
    return originalView;
}


/// 多个空格替换
/// @param text 替换空格文字
+(NSString *)replacingSpaceWithText:(NSString *)text
{
    NSError *error = nil;
    NSRegularExpression *regex = [NSRegularExpression regularExpressionWithPattern:@"\\s{3,}" options:NSRegularExpressionCaseInsensitive error:&error];
    NSArray *arr = [regex matchesInString:text options:NSMatchingReportCompletion range:NSMakeRange(0, [text length])];
    arr = [[arr reverseObjectEnumerator] allObjects];
    for (NSTextCheckingResult *str in arr)
    {
        text = [text stringByReplacingCharactersInRange:[str range] withString:@" "];
    }
    return text;
}

+ (void)configWebViewJSMethod:(WKUserContentController *)contentVc delegate:(id <WKScriptMessageHandler>)vc{
    [contentVc addScriptMessageHandler:vc name:@"csdnapptrack"];
    [contentVc addScriptMessageHandler:vc name:@"changenavigationcolor"];
    [contentVc addScriptMessageHandler:vc name:@"csdnshowclose"];
    [contentVc addScriptMessageHandler:vc name:@"csdnshowshare"];
    [contentVc addScriptMessageHandler:vc name:@"csdnjumpnewpage"];
    [contentVc addScriptMessageHandler:vc name:@"csdnshowbubble"];
    [contentVc addScriptMessageHandler:vc name:@"shareWeb"];
    [contentVc addScriptMessageHandler:vc name:@"csdnrefreshurl"];
    [contentVc addScriptMessageHandler:vc name:@"csdnpaypurchase"];
    [contentVc addScriptMessageHandler:vc name:@"csdnpayrecharge"];
    [contentVc addScriptMessageHandler:vc name:@"csdndownloadfile"];
    [contentVc addScriptMessageHandler:vc name:@"getShareImg"];
    [contentVc addScriptMessageHandler:vc name:@"csdnapppop"];
    [contentVc addScriptMessageHandler:vc name:@"csdnappStartTinyapp"];

}
+ (void)removeWebViewJSMethod:(WKUserContentController *)contentVc{
    [contentVc removeScriptMessageHandlerForName:@"csdnapptrack"];
    [contentVc removeScriptMessageHandlerForName:@"changenavigationcolor"];
    [contentVc removeScriptMessageHandlerForName:@"csdnshowclose"];
    [contentVc removeScriptMessageHandlerForName:@"csdnshowshare"];
    [contentVc removeScriptMessageHandlerForName:@"csdnjumpnewpage"];
    [contentVc removeScriptMessageHandlerForName:@"csdnshowbubble"];
    [contentVc removeScriptMessageHandlerForName:@"shareWeb"];
    [contentVc removeScriptMessageHandlerForName:@"csdnrefreshurl"];
    [contentVc removeScriptMessageHandlerForName:@"csdnpaypurchase"];
    [contentVc removeScriptMessageHandlerForName:@"csdnpayrecharge"];
    [contentVc removeScriptMessageHandlerForName:@"csdndownloadfile"];
    [contentVc removeScriptMessageHandlerForName:@"getShareImg"];
    [contentVc removeScriptMessageHandlerForName:@"csdnapppop"];
    [contentVc removeScriptMessageHandlerForName:@"csdnappStartTinyapp"];
    

}

+ (NSString *)chindDateFormate:(NSDate *)update{
   
    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
    NSString *destDateString = [dateFormatter stringFromDate:update];
    return destDateString;
}

+ (NSString *)homePath {
    return NSHomeDirectory();
}

+ (NSString *)appPath {
    NSArray * paths = NSSearchPathForDirectoriesInDomains(NSApplicationDirectory, NSUserDomainMask, YES);
    return [paths objectAtIndex:0];
}

+ (NSString *)docPath {
    NSArray * paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    return [paths objectAtIndex:0];
}

+ (NSString *)libPrefPath {
    NSArray * paths = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);
    return [[paths objectAtIndex:0] stringByAppendingFormat:@"/Preferences"];
}

+ (NSString *)libCachePath {
    NSArray * paths = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);
    return [[paths objectAtIndex:0] stringByAppendingFormat:@"/Caches"];
}

+ (NSString *)tmpPath {
    return [NSHomeDirectory() stringByAppendingFormat:@"/tmp"];
}

+ (NSString *)iapReceiptPath {
    
    NSString *path = [[self libPrefPath] stringByAppendingFormat:@"/EACEF35FE363A75A"];
    [self hasLive:path];
    return path;
}

+ (BOOL)hasLive:(NSString *)path
{
    if ( NO == [[NSFileManager defaultManager] fileExistsAtPath:path] )
    {
        return [[NSFileManager defaultManager] createDirectoryAtPath:path
                                         withIntermediateDirectories:YES
                                                          attributes:nil
                                                               error:NULL];
    }
    
    return YES;
}

//view转成image
+ (UIImage*)imageWithUIView:(UIView*)view
{
    UIGraphicsBeginImageContextWithOptions(view.bounds.size, NO, UIScreen.mainScreen.scale);
    [view.layer renderInContext:UIGraphicsGetCurrentContext()];
    UIImage *snapshotImage = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    return snapshotImage;
}


/// 获取跟控制器
+ (UIViewController *)cn_getRootViewController
{

    UIWindow* window = [[[UIApplication sharedApplication] delegate] window];
    NSAssert(window, @"The window is empty");
    return window.rootViewController;
}


/// 获取当前控制器
+ (UIViewController *)cn_findVisibleViewController
{
    
    UIViewController* currentViewController = [self cn_getRootViewController];

    BOOL runLoopFind = YES;
    while (runLoopFind) {
        if (currentViewController.presentedViewController) {
            currentViewController = currentViewController.presentedViewController;
        } else {
            if ([currentViewController isKindOfClass:[UINavigationController class]]) {
                currentViewController = ((UINavigationController *)currentViewController).visibleViewController;
            } else if ([currentViewController isKindOfClass:[UITabBarController class]]) {
                currentViewController = ((UITabBarController* )currentViewController).selectedViewController;
            } else if([currentViewController isKindOfClass:[WMPageController class]]){
                currentViewController = ((WMPageController* )currentViewController).currentViewController;
            }else{
                break;
            }
        }
    }
    
    return currentViewController;
}

/**

 @param quality 视频质量的枚举
 @return 视频质量的描述
 */
+ (NSString *)stringWithQuality:(NSString *)quality{
    if ([quality isEqualToString:@"fd"]) {
        return @"流畅";
    }else if ([quality isEqualToString:@"ld"]) {
        return @"标清";
    }else if ([quality isEqualToString:@"sd"]) {
        return @"高清" ;
    }else if ([quality isEqualToString:@"hd"]) {
        return @"超清" ;
    }else if ([quality isEqualToString:@"od"]) {
        return @"原画";
    }
    return NSLocalizedString(@"不明", nil);
}

+ (id)getJsonDataJsonname:(NSString *)jsonname
{
    NSString *path = [[NSBundle mainBundle] pathForResource:jsonname ofType:@"json"];
    NSData *jsonData = [[NSData alloc] initWithContentsOfFile:path];
    NSError *error;
    id jsonObj = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingMutableContainers error:&error];
    if (!jsonData || error) {
        //DLog(@"JSON解码失败");
        return nil;
    } else {
        return jsonObj;
    }
}

/// 获取WKWebView加载时间
/// @param infoWebView webView
+(void)jsTimingWithWKWebView:(WKWebView *)infoWebView
{
    //属性说明
    //    navigationStart：浏览器处理当前网页的启动时间
    //    fetchStart：浏览器发起http请求读取文档的毫秒时间戳。
    //    domainLookupStart：域名查询开始时的时间戳。
    //    domainLookupEnd：域名查询结束时的时间戳。
    //    connectStart：http请求开始向服务器发送的时间戳。
    //    connectEnd：浏览器与服务器连接建立（握手和认证过程结束）的毫秒时间戳。
    //    requestStart：浏览器向服务器发出http请求时的时间戳。或者开始读取本地缓存时。
    //    responseStart：浏览器从服务器（或读取本地缓存）收到第一个字节时的时间戳。
    //    responseEnd：浏览器从服务器收到最后一个字节时的毫秒时间戳。
    //    domLoading：浏览器开始解析网页DOM结构的时间。
    //    domInteractive：网页dom树创建完成，开始加载内嵌资源的时间。
    //    domContentLoadedEventStart：网页DOMContentLoaded事件发生时的时间戳。
    //    domContentLoadedEventEnd：网页所有需要执行的脚本执行完成时的时间，domReady的时间。
    //    domComplete：网页dom结构生成时的时间戳。
    //    loadEventStart：当前网页load事件的回调函数开始执行的时间戳。
    //    loadEventEnd：当前网页load事件的回调函数结束运行时的时间戳。
    if (@available(iOS 10.0, *)) {
        [infoWebView evaluateJavaScript:@"JSON.stringify(window.performance.timing.toJSON())" completionHandler:^(id _Nullable timingStr, NSError * _Nullable error) {
            if (error == nil && timingStr != nil) {
                //格式化时间
                [self parseJSTimingDictionary:[CSDNTool dictionaryWithJsonString:timingStr]];
            }else{
                NSLog(@"WKWebView Load Performance JS Faild!");
            }
        }];
    }else{
        NSString *jsFuncStr =
        @"function flatten(obj) {\
        var ret = {};\
        for (var i in obj) {\
        ret[i] = obj[i];\
        }\
        return ret;}\
        ";
        
        [infoWebView evaluateJavaScript:jsFuncStr completionHandler:^(id _Nullable resultStr, NSError * _Nullable error) {
            if (error == nil && resultStr != nil) {
                [infoWebView evaluateJavaScript:@"JSON.stringify(flatten(window.performance.timing))" completionHandler:^(id _Nullable timingStr, NSError * _Nullable error) {
                    if (error == nil && timingStr != nil) {
                        [self parseJSTimingDictionary:[CSDNTool dictionaryWithJsonString:timingStr]];
                    }else{
                        NSLog(@"WKWebView Load Performance JS Faild!");
                    }
                }];
            }else{
                NSLog(@"WKWebView evaluateJavaScript Faild!");
            }
        }];
    }
}

+(void)parseJSTimingDictionary:(NSDictionary *)dict
{
    NSLog(@"describing%@\n",dict);
    NSTimeInterval domainLookupStart = [dict[@"domainLookupStart"] doubleValue];
    NSTimeInterval domainLookupEnd = [dict[@"domainLookupEnd"] doubleValue];
    NSTimeInterval connectStart = [dict[@"connectStart"] doubleValue];
    NSTimeInterval connectEnd = [dict[@"connectEnd"] doubleValue];
    NSTimeInterval responseStart = [dict[@"responseStart"] doubleValue];
    NSTimeInterval responseEnd = [dict[@"responseEnd"] doubleValue];
    NSTimeInterval domInteractive = [dict[@"domInteractive"] doubleValue];
    NSTimeInterval domComplete = [dict[@"domComplete"] doubleValue];
    NSTimeInterval fetchStart = [dict[@"fetchStart"] doubleValue];
    NSTimeInterval domLoading = [dict[@"domLoading"] doubleValue];
    NSTimeInterval domContentLoadedEventEnd = [dict[@"domContentLoadedEventEnd"] doubleValue];
    NSTimeInterval loadEventStart = [dict[@"loadEventStart"] doubleValue];
    NSTimeInterval loadEventEnd = [dict[@"loadEventEnd"] doubleValue];
    NSTimeInterval redirectStart = [dict[@"redirectStart"] doubleValue];
    NSTimeInterval redirectEnd = [dict[@"redirectEnd"] doubleValue];
    NSTimeInterval navigationStart = [dict[@"navigationStart"] doubleValue];
    NSTimeInterval unloadEventStart = [dict[@"unloadEventStart"] doubleValue];
    NSTimeInterval unloadEventEnd = [dict[@"unloadEventEnd"] doubleValue];
    
    NSTimeInterval dnstiming = domainLookupEnd - domainLookupStart; //DSN解析时间
    NSTimeInterval tcptiming = connectEnd - connectStart; //TCP链接耗时(完成握手)
    NSTimeInterval requesttiming = responseEnd - responseStart; //request请求耗时
    NSTimeInterval domtiming = domComplete - domInteractive; //解析dom树耗时
    NSTimeInterval wheetScreentiming = domLoading - fetchStart; //白屏时间
    NSTimeInterval firstscreentime = domLoading - fetchStart; //首屏时间
    NSTimeInterval domreadytiming = domContentLoadedEventEnd - fetchStart; //dom ready时间
    NSTimeInterval domloadtiming = loadEventEnd - loadEventStart; //dom load时间
    NSTimeInterval onloadtiming = loadEventEnd - fetchStart; //onload总时间（整页时间）
    NSTimeInterval redirecttime = redirectEnd - redirectStart; //重定向时间
    NSTimeInterval domstartstoloadtime = responseEnd - navigationStart; //DOM开始加载前所花费时间
    NSTimeInterval domloadingcompletiontime = domComplete - domLoading; //DOM加载完成时间
    NSTimeInterval domanalysiscompletiontime = domInteractive - domLoading; //DOM结构解析完成时间
    NSTimeInterval loadPagetime = loadEventEnd - navigationStart;// 页面加载完成的时间，用户等待页面可用的时间
    NSTimeInterval ttfbtime = responseStart - navigationStart;// 读取页面第一个字节的时间
    NSTimeInterval appcachetime = domainLookupStart - fetchStart;// DNS 缓存时间
    NSTimeInterval unloadEvent = unloadEventEnd - unloadEventStart;// 卸载页面的时间
    NSTimeInterval fullloadtime = domComplete - navigationStart;//完全加载
    NSTimeInterval activetime = domInteractive - navigationStart;//可交互时间
    
    NSMutableString *moreTimeStr = [[NSMutableString alloc]init];
    [moreTimeStr appendFormat:@"dnstiming(DNS查询耗时):%lf(ms)\n",dnstiming];
    [moreTimeStr appendFormat:@"tcptiming(TCP链接耗时):%lf(ms)\n",tcptiming];
    [moreTimeStr appendFormat:@"requesttiming(request请求耗时):%lf(ms)\n",requesttiming];
    [moreTimeStr appendFormat:@"domtiming(解析dom树耗时):%lf(ms)\n",domtiming];
    [moreTimeStr appendFormat:@"domreadytiming(dom ready时间):%lf(ms)\n",domreadytiming];
    [moreTimeStr appendFormat:@"domloadtiming(dom load时间):%lf(ms)\n",domloadtiming];
    [moreTimeStr appendFormat:@"onloadtiming(onload总时间（整页时间）):%lf(ms)\n",onloadtiming];
    [moreTimeStr appendFormat:@"redirecttime(重定向时间):%lf(ms)\n",redirecttime];
    [moreTimeStr appendFormat:@"domstartstoloadtime(DOM开始加载前所花费时间):%lf(ms)\n",domstartstoloadtime];
    [moreTimeStr appendFormat:@"domloadingcompletiontime(DOM加载完成时间):%lf(ms)\n",domloadingcompletiontime];
    [moreTimeStr appendFormat:@"domanalysiscompletiontime(DOM结构解析完成时间):%lf(ms)\n",domanalysiscompletiontime];
    [moreTimeStr appendFormat:@"loadPagetime(页面加载完成的时间，用户等待页面可用的时间):%lf(ms)\n",loadPagetime];
    [moreTimeStr appendFormat:@"ttfbtime(读取页面第一个字节的时间):%lf(ms)\n",ttfbtime];
    [moreTimeStr appendFormat:@"appcachetime(DNS 缓存时间):%lf(ms)\n",appcachetime];
    [moreTimeStr appendFormat:@"unloadEvent(卸载页面的时间):%lf(ms)\n",unloadEvent];
    [moreTimeStr appendFormat:@"firstscreentime(首屏时间):%lf(ms)\n",firstscreentime];
    [moreTimeStr appendFormat:@"wheetScreentiming(白屏时间):%lf(ms)\n",wheetScreentiming];
    [moreTimeStr appendFormat:@"fullloadtime(完全加载时间):%lf(ms)\n",fullloadtime];
    [moreTimeStr appendFormat:@"activetime(可交互时间):%lf(ms)\n",activetime];
    NSLog(@"%@",moreTimeStr);
}

+ (NSDictionary *)getUtmParamsWithURL:(NSURL *)url{
    NSDictionary *urlParmas = [self parameterWithURL:url];
    
    NSMutableDictionary *utmParams = [NSMutableDictionary dictionary];
    [urlParmas enumerateKeysAndObjectsUsingBlock:^(id  _Nonnull key, id  _Nonnull obj, BOOL * _Nonnull stop) {
        if ([key hasPrefix:@"utm_"]) {
            [utmParams setValue:obj forKey:key];
        }
    }];
    return utmParams;
}

@end
